package com.media.publish;

import android.annotation.SuppressLint;
import android.content.Intent;
import android.graphics.Rect;
import android.opengl.GLSurfaceView;
import android.os.AsyncTask;
import android.os.Bundle;
import android.os.Handler;
import android.text.TextUtils;
import android.view.View;
import android.view.ViewTreeObserver;
import android.view.WindowManager;
import android.widget.Button;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.TextView;

import androidx.annotation.Nullable;
import androidx.appcompat.app.AppCompatActivity;

import com.baselibrary.manager.DialogManager;
import com.baselibrary.utils.DoubleUtils;
import com.baselibrary.utils.ToastUtils;
import com.baselibrary.view.CustomProgressDialog;
import com.media.R;
import com.media.publish.video_view.VideoFrameListView;
import com.nostra13.universalimageloader.core.ImageLoader;
import com.qiniu.pili.droid.shortvideo.PLMediaFile;
import com.qiniu.pili.droid.shortvideo.PLShortVideoEditor;
import com.qiniu.pili.droid.shortvideo.PLShortVideoTrimmer;
import com.qiniu.pili.droid.shortvideo.PLVideoEditSetting;
import com.qiniu.pili.droid.shortvideo.PLVideoSaveListener;

import java.io.File;

import com.media.publish.bean.EditVideoAttributeBean;
import com.media.publish.utils.Config;
import com.media.publish.utils.LoadFrameTask;
import com.media.publish.utils.StickerImageViewTwo;
import com.media.publish.utils.StickerTextView;


/**
 * 视频剪辑模块，包含了视频剪辑、区域剪裁以及旋转等功能
 * <p>
 * 旋转功能由于 SDK 目前不支持预览，因此需要结合可以旋转的播放器来进行预览，最终保存时再带入角度信息
 */
public class VideoTrimActivity extends AppCompatActivity implements VideoFrameListView.OnVideoRangeChangedListener {
    private static final int FRAME_COUNT = 10;

    // 用于视频的剪辑
    private PLShortVideoTrimmer mShortVideoTrimmer;
    // 用于视频的区域剪裁和旋转，，这个还不能删除，用它来保存裁剪后的视频
    private PLMediaFile mMediaFile;

    private GLSurfaceView mPreview;
    private VideoFrameListView mVideoFrameListView;
    private TextView mStartTimeText;
    private TextView mDurationText;
    private TextView mEndTimeText;
    private CustomProgressDialog mProcessingDialog;

    private long mSelectedBeginMs;
    private long mSelectedEndMs;
    private long mDurationMs;

    private int mRotation = 0;
    public static final String VIDEO_PATH = "videoPath";
    public static final String VIDEO_PATH_OLD = "VIDEO_PATH_OLD";
    public static final String IS_CROP = "is_crop";

    private LoadFrameTask mLoadFrameTask;

    private PLShortVideoEditor mShortVideoEditor;
    private LinearLayout mLlCropSection;
    private String mMp4Path;//参加过后视频路径 裁剪之后，点击 完成

    private Handler tHandler = new Handler();
    private EditVideoAttributeBean mEditVideoAttrBean;
    private boolean isCrop;
    private String mVideoPathOld;//原视频路径 裁剪之后，点击 back 建 返回，需要 返回到原来的视频
    private boolean mIsPlaying = true;
    private ImageView mPlayControlIv;
    private String mMp4pathMusicName = "";
    private String mMp4pathMusicId = "";
    private boolean isAlbum;
    private String cropFile;
    //是否通过eventbus 传值
    private boolean isPassEventbus;
    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN, WindowManager.LayoutParams.FLAG_FULLSCREEN);
        setContentView(R.layout.activity_video_trim);
        intiView();
        mVideoPathOld = getIntent().getStringExtra(VIDEO_PATH_OLD);
        init(getIntent().getStringExtra(VIDEO_PATH));
    }

    private void intiView() {
        isCrop = getIntent().getBooleanExtra(IS_CROP, false);
        isAlbum = getIntent().getBooleanExtra("isAlbum", false);
        isPassEventbus = getIntent().getBooleanExtra("isPassEventbus", false);
        mMp4pathMusicName = getIntent().getStringExtra(VideoEditActivity.MP4_PATH_MUSIC_NAME);
        mMp4pathMusicId = getIntent().getStringExtra(VideoEditActivity.MP4_PATH_MUSIC_ID);

        mEditVideoAttrBean = (EditVideoAttributeBean) getIntent().getSerializableExtra("editVideoAttribute");
        mStartTimeText = findViewById(R.id.start_time_text);
        mEndTimeText = findViewById(R.id.end_time_text);
        mDurationText = findViewById(R.id.duration_text);
        mLlCropSection = findViewById(R.id.ll_crop_section);
        Button mConfirmBtn = findViewById(R.id.confirm_btn);
        mPlayControlIv = findViewById(R.id.play_control_iv);
        mLlCropSection.setAlpha(0.2f);
        mLlCropSection.setEnabled(false);

        /*if (isCrop) {
            Drawable myDraw = getResources().getDrawable(R.drawable.bg_rectangle_d29);
            mConfirmBtn.setBackground(myDraw);
        } else {
            Drawable myDraw = getResources().getDrawable(R.drawable.rectangle_btn_background_two);
            mConfirmBtn.setBackground(myDraw);
        }*/
        mPreview = findViewById(R.id.preview);
        mPreview.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                updatePlayStatus(!mIsPlaying);
            }
        });
        mVideoFrameListView = findViewById(R.id.video_frames_view);
        mVideoFrameListView.setOnVideoRangeChangedListener(this);
        mProcessingDialog = new CustomProgressDialog();
        mProcessingDialog.createLoadingDialog(VideoTrimActivity.this);
        mProcessingDialog.setCancelable(false); // 设置是否可以通过点击Back键取消
        mProcessingDialog.setCanceledOnTouchOutside(false); // 设置在点击Dialog外是否取消Dialog进度条
    }


    public void onClickTrim(View v) {
        if (mMediaFile == null || mMediaFile.getDurationMs() > Config.VIDEO_MAXDURATIONMS) {
            ToastUtils.showShort(this,"视频最长300秒，请先完成截取");
            return;
        }
        if (!isCrop) {
            ToastUtils.showShort(this,"请先完成截取");
            return;
        }
        if (DoubleUtils.isFastDoubleClick()) return;
        Intent intent = new Intent(VideoTrimActivity.this, VideoEditActivity.class);
        intent.putExtra("MP4_PATH", mMp4Path);
        intent.putExtra(VideoEditActivity.MP4_PATH_MUSIC_NAME, mMp4pathMusicName);
        intent.putExtra(VideoEditActivity.MP4_PATH_MUSIC_ID, mMp4pathMusicId);
        intent.putExtra("isPassEventbus",isPassEventbus);
        if (mEditVideoAttrBean != null) {
            intent.putExtra("editVideoAttribute", mEditVideoAttrBean);
        }
        startActivity(intent);
        finish();
    }

    public void onClickBack(View v) {
        DialogManager.showConfirmDialog(this, "", "是否放弃当前编辑的内容？", "放弃", "取消", new DialogManager.Listener() {
            @Override
            public void onItemLeft() {
                if (isAlbum) {
                    try {
                        if (!TextUtils.isEmpty(cropFile)) {
                            new File(cropFile).delete();
                        }
                    } catch (Exception e) {
                        e.getMessage();
                    }
                    finish();
                    return;
                }

                Intent intent = new Intent(VideoTrimActivity.this, VideoEditActivity.class);
                intent.putExtra("MP4_PATH", mVideoPathOld);
                intent.putExtra(VideoEditActivity.MP4_PATH_MUSIC_NAME, mMp4pathMusicName);
                intent.putExtra(VideoEditActivity.MP4_PATH_MUSIC_ID, mMp4pathMusicId);
                intent.putExtra("isPassEventbus",isPassEventbus);
                if (mEditVideoAttrBean != null) {
                    intent.putExtra("editVideoAttribute", mEditVideoAttrBean);
                }
                startActivity(intent);
                finish();
            }

            @Override
            public void onItemRight() {

            }
        });

    }

    @Override
    public void onBackPressed() {
        onClickBack(null);
    }

    private void init(String videoPath) {
        mMp4Path = videoPath;
        mShortVideoTrimmer = new PLShortVideoTrimmer(this, videoPath, Config.TRIM_FILE_PATH);

        mVideoFrameListView.getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
            @Override
            public void onGlobalLayout() {
                mVideoFrameListView.getViewTreeObserver().removeOnGlobalLayoutListener(this);
                final int sliceEdge = mVideoFrameListView.getWidth() / FRAME_COUNT;

                mLoadFrameTask = new LoadFrameTask(VideoTrimActivity.this, mMediaFile, FRAME_COUNT, sliceEdge, sliceEdge, bitmap -> {
                    if (bitmap != null) {
                        mVideoFrameListView.addBitmap(bitmap);
                    }
                });
                mLoadFrameTask.executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR);
            }
        });
        initVideoData(videoPath);
        mVideoFrameListView.init(this, mMediaFile, FRAME_COUNT);
    }

    public void initVideoData(String mSDCardVideoPath) {
        mMediaFile = new PLMediaFile(mSDCardVideoPath);
        PLVideoEditSetting setting = new PLVideoEditSetting();
        setting.setSourceFilepath(mSDCardVideoPath);
        setting.setDestFilepath(Config.EDITED_FILE_PATH);
        setting.setGifPreviewEnabled(false);
        mShortVideoEditor = new PLShortVideoEditor(mPreview);
        mShortVideoEditor.setVideoEditSetting(setting);
        mSelectedEndMs = mShortVideoEditor.getDurationMs();
        mDurationMs = mSelectedEndMs;
        mStartTimeText.setText(formatTime(0));
        mEndTimeText.setText(formatTime(mMediaFile.getDurationMs()));
        if (mMediaFile.getDurationMs() <= Config.VIDEO_MAXDURATIONMS) {//为啥截取下来的少一秒，所以这里加一秒
            mDurationText.setText(formatTime(mMediaFile.getDurationMs()));
        } else {
            mSelectedEndMs = Config.VIDEO_MAXDURATIONMS;
            mDurationText.setText(formatTime(1000 * 300));
            mLlCropSection.setAlpha(1f);
            mLlCropSection.setEnabled(true);
        }

        setVideoAttr();
    }

    private void setVideoAttr() {
        if (mEditVideoAttrBean != null) {
            if (mEditVideoAttrBean.getVideoStickerAttr() != null) {
                setViewInfo(3);
            }
            if (mEditVideoAttrBean.getFilterAttr() != null) {
                setViewInfo(1);
            }
            if (mEditVideoAttrBean.getVideoAddTextAttr() != null) {
                setViewInfo(2);
            }
        }
    }

    private void play() {
        try {
            if (mPreview != null && mShortVideoEditor != null) {
                mShortVideoEditor.seekTo((int) mSelectedBeginMs);
                mShortVideoEditor.startPlayback();
                startTrackPlayProgress();
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    private void startTrackPlayProgress() {
        tHandler.removeCallbacksAndMessages(null);
        tHandler.postDelayed(new Runnable() {
            @Override
            public void run() {
                if (mShortVideoEditor.getCurrentPosition() >= mSelectedEndMs) {
                    mShortVideoEditor.seekTo((int) mSelectedBeginMs);
                }
                tHandler.postDelayed(this, 100);
            }
        }, 100);
    }


    @SuppressLint("DefaultLocale")
    private String formatTime(long timeMs) {
        String time;
        timeMs = timeMs / 1000;
        if (timeMs < 60) {
            time = String.format("00:%02d", timeMs % 60);
        } else if (timeMs < 3600) {
            time = String.format("%02d:%02d", timeMs / 60, timeMs % 60);
        } else {
            time = String.format("%02d:%02d:%02d", timeMs / 3600, timeMs % 3600 / 60, timeMs % 60);
        }
        return time;
    }

    private void updateRangeText(long startTime, long endTime) {
        mStartTimeText.setText(formatTime(startTime));
        mEndTimeText.setText(formatTime(endTime));
        mDurationText.setText(formatTime(endTime - startTime));
        if ((startTime != 0 || mDurationMs != endTime) && endTime - startTime < Config.VIDEO_MAXDURATIONMS) {
            mLlCropSection.setAlpha(1f);
            mLlCropSection.setEnabled(true);
        } else {
            mLlCropSection.setAlpha(0.2f);
            mLlCropSection.setEnabled(false);
        }
        play();
    }

    @Override
    public void onVideoRangeChangeKeyDown() {

    }

    @Override
    public void onVideoRangeChanged(long startTime, long endTime) {
        mSelectedBeginMs = startTime;
        mSelectedEndMs = endTime;
        updateRangeText(mSelectedBeginMs, mSelectedEndMs);
    }

    @Override
    public void onPointerCaptureChanged(boolean hasCapture) {

    }

    /**
     * 保存这一段
     *
     * @param view
     */
    public void onClickCrop(View view) {
        if (mSelectedEndMs - mSelectedBeginMs < 3 * 1000) {
            ToastUtils.showShort(this,"视频最短要大于3秒哦~");
            return;
        }
        if (mSelectedEndMs - mSelectedBeginMs > Config.VIDEO_MAXDURATIONMS) {
            ToastUtils.showShort(this,"视频最长不能超过300秒哦~");
            return;
        }
        if (DoubleUtils.isFastDoubleClick()) return;
        mProcessingDialog.show();

        mShortVideoTrimmer.trim(mSelectedBeginMs, mSelectedEndMs, PLShortVideoTrimmer.TRIM_MODE.FAST, new PLVideoSaveListener() {
            @Override
            public void onSaveVideoSuccess(final String path) {
                runOnUiThread(() -> {
                    mProcessingDialog.dismiss();
                    int dstWidth = mMediaFile.getVideoWidth();
                    int dstHeight = mMediaFile.getVideoHeight();
                    cropFile = path;
                    mProcessingDialog.dismiss();
                    Intent cropIntent = new Intent(VideoTrimActivity.this, VideoTrimActivity.class);
                    cropIntent.putExtra(VideoTrimActivity.VIDEO_PATH, path);
                    cropIntent.putExtra(VideoTrimActivity.VIDEO_PATH_OLD, mVideoPathOld);
                    cropIntent.putExtra(VideoEditActivity.MP4_PATH_MUSIC_NAME, mMp4pathMusicName);
                    cropIntent.putExtra(VideoEditActivity.MP4_PATH_MUSIC_ID, mMp4pathMusicId);
                    cropIntent.putExtra("isAlbum", isAlbum);
                    cropIntent.putExtra(VideoTrimActivity.IS_CROP, true);
                    cropIntent.putExtra("isPassEventbus",isPassEventbus);
                    if (mEditVideoAttrBean != null) {
                        cropIntent.putExtra("editVideoAttribute", mEditVideoAttrBean);
                    }
                    startActivity(cropIntent);
                    finish();
               /*     mShortVideoTranscoder.transcode(dstWidth, dstHeight, mMediaFile.getVideoBitrate(), mRotation, new PLVideoSaveListener() {

                        @Override
                        public void onSaveVideoSuccess(final String path1) {
                            runOnUiThread(() -> {
                                cropFile = path1;
                                mProcessingDialog.dismiss();
                                Intent cropIntent = new Intent(VideoTrimActivity.this, VideoTrimActivity.class);
                                cropIntent.putExtra(VideoTrimActivity.VIDEO_PATH, path1);
                                cropIntent.putExtra(VideoTrimActivity.VIDEO_PATH_OLD, mVideoPathOld);
                                cropIntent.putExtra(VideoEditActivity.MP4_PATH_MUSIC_NAME, mMp4pathMusicName);
                                cropIntent.putExtra(VideoEditActivity.MP4_PATH_MUSIC_ID, mMp4pathMusicId);
                                cropIntent.putExtra("isAlbum", isAlbum);
                                cropIntent.putExtra(VideoTrimActivity.IS_CROP, true);
                                if (mEditVideoAttrBean != null) {
                                    cropIntent.putExtra("editVideoAttribute", mEditVideoAttrBean);
                                }
                                startActivity(cropIntent);
                                finish();
                            });
                        }

                        @Override
                        public void onSaveVideoFailed(int i) {
                        }

                        @Override
                        public void onSaveVideoCanceled() {
                            mProcessingDialog.dismiss();
                        }

                        @Override
                        public void onProgressUpdate(final float percentage) {
//                            runOnUiThread(() -> mProcessingDialog.setMsg("处理中..." + (int) (50 + 100 * percentage / 2) + "%"));
                            mProcessingDialog.show();
                        }
                    });*/
                });
            }

            @Override
            public void onSaveVideoFailed(final int errorCode) {
                runOnUiThread(() -> {
                    mProcessingDialog.dismiss();
                    ToastUtils.showShort(VideoTrimActivity.this, errorCode);
                });
            }

            @Override
            public void onSaveVideoCanceled() {
                mProcessingDialog.dismiss();
            }

            @Override
            public void onProgressUpdate(final float percentage) {
//                runOnUiThread(() -> mProcessingDialog.setMsg((int) ((mRotation != 0) ? 100 * percentage / 2 : 100 * percentage)));
                mProcessingDialog.show();
            }
        });
    }


    public void setViewInfo(int viewType) {
        if (mShortVideoEditor == null)
            return;
        switch (viewType) {
            case 1://滤镜
                mShortVideoEditor.setBuiltinFilter(mEditVideoAttrBean.getFilterAttr());
                break;
            case 2://文字
                EditVideoAttributeBean.StickerTextViewBean videoAddText = mEditVideoAttrBean.getVideoAddTextAttr();
                StickerTextView mStickerTextView = new StickerTextView(this);
                mVideoFrameListView.post(() -> {
                    mStickerTextView.setEditable(false);
                    mStickerTextView.setRect(new Rect(videoAddText.left, videoAddText.top, videoAddText.right, videoAddText.bottom));
                    mStickerTextView.setDegree(videoAddText.rotate);
                    mStickerTextView.setScale(videoAddText.scale);
                    mStickerTextView.setTextColor(videoAddText.color);
                    mStickerTextView.setText(videoAddText.content);
                    mStickerTextView.setTextSize(videoAddText.textSize);
                    mShortVideoEditor.addTextView(mStickerTextView);
                });
                break;
            case 3://贴纸
                ImageView imageView = new ImageView(this);
                EditVideoAttributeBean.StickerImageViewTwoBean videoStickerAttr = mEditVideoAttrBean.getVideoStickerAttr();
                ImageLoader.getInstance().displayImage(videoStickerAttr.drawablePath, imageView);
                StickerImageViewTwo mStickerImageView = new StickerImageViewTwo(this);
                mVideoFrameListView.post(() -> {
                    mStickerImageView.setSelected(false);
                    mStickerImageView.setTouchable(false);
                    mStickerImageView.setImageDrawable(imageView.getDrawable());
                    mStickerImageView.setLocation(videoStickerAttr.left, videoStickerAttr.top, videoStickerAttr.right, videoStickerAttr.bottom);
                    mStickerImageView.setImageDegree(videoStickerAttr.rotate);
                    mStickerImageView.setImageScale(videoStickerAttr.scale);
                    mShortVideoEditor.addImageView(mStickerImageView);
                });
                break;
            case 4://音乐
                break;
        }
    }

    private void updatePlayStatus(boolean isPlaying) {
        if (isPlaying) {
            mShortVideoEditor.startPlayback();
            mPlayControlIv.setVisibility(View.GONE);
        } else {
            mShortVideoEditor.pausePlayback();
            mPlayControlIv.setVisibility(View.VISIBLE);
        }
        mIsPlaying = isPlaying;
    }

    @Override
    protected void onResume() {
        super.onResume();
        play();
    }

    @Override
    protected void onPause() {
        super.onPause();
        updatePlayStatus(false);
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();
        if (mLoadFrameTask != null && mLoadFrameTask.getStatus() == AsyncTask.Status.RUNNING) {
            mLoadFrameTask.cancel(true);
            mLoadFrameTask = null;
        }
        if (mShortVideoTrimmer != null) {
            mShortVideoTrimmer.destroy();
        }
        if (mMediaFile != null) {
            mMediaFile.release();
        }
        if (mShortVideoEditor != null) {
            mShortVideoEditor.stopPlayback();
        }
        if (mProcessingDialog != null) {
            mProcessingDialog.dismiss();
        }

    }
}
